import Router from '@koa/router'
import { hexoid } from 'hexoid'
import fs from 'node:fs'
import path from 'node:path'
import KnowledgeBaseFile, {
    KnowledgeBaseFileStatus,
} from '../models/KnowledgeBaseFile'
import { saveToVectorStore } from './knowledgeBase'
import { toUrl } from '../utils/uploadUrlTrans'

const toId = hexoid()

interface IFile {
    fieldname: string
    originalname: string
    encoding: string
    mimetype: string
    buffer: Buffer
    size: number
}

const saveFiles = (files: any[], folder = '') => {
    const uploadDir = path.resolve('./public/uploads', folder)

    // 如果文件夹不存在则创建
    if (!fs.existsSync(uploadDir)) {
        fs.mkdirSync(uploadDir, {
            recursive: true,
        })
    }

    const result: {
        originalFilename: string
        newFilename: string
        url: string
    }[] = []

    // 保存文件
    for (const file of files) {
        const extName = path.extname(file.originalname)
        const newFilename = toId() + extName
        const filePath = path.join(uploadDir, newFilename)
        fs.writeFileSync(filePath, file.buffer)
        result.push({
            originalFilename: Buffer.from(file.originalname, 'latin1').toString(
                'utf8'
            ),
            newFilename,
            url: toUrl(`/uploads/${folder}/${newFilename}`),
        })
    }
    return result
}

// 文件上传，用于文章，头像，各种封面
export const upload: Router.Middleware = async (ctx) => {
    if (!ctx.state.user) {
        ctx.body = { success: false, msg: '未登录' }
        return
    }

    const { id } = ctx.state.user
    const { folder } = ctx.request.body

    if (!id || !folder) {
        ctx.body = { success: false, msg: '参数错误' }
        return
    }

    const reqFiles = ctx.files as IFile[]

    if (!reqFiles) {
        ctx.body = { success: false, msg: '参数错误' }
        return
    }

    const result = saveFiles(reqFiles, folder)

    try {
        ctx.body = { success: true, msg: '上传成功', data: result }
    } catch (error) {
        ctx.body = { success: false, msg: '发生错误' }
    }
}

// 文件上传，用于知识库文件，文件上传后即可开始向量化
export const uploadKnowledgeBase: Router.Middleware = async (ctx) => {
    if (!ctx.state.user) {
        ctx.body = { success: false, msg: '未登录' }
        return
    }

    // 参数验证
    const { id } = ctx.state.user
    const { type, collectionName } = ctx.request.body
    let { knowledgeBaseId } = ctx.request.body
    if (!id || !knowledgeBaseId || !type || !collectionName) {
        ctx.body = { success: false, msg: '参数错误' }
        return
    }
    knowledgeBaseId = +knowledgeBaseId

    // 保存文件
    const reqFiles = ctx.files as IFile[]
    if (!reqFiles) {
        ctx.body = { success: false, msg: '参数错误' }
        return
    }

    try {
        const result = saveFiles(reqFiles, 'knowledge-base')
        // 在数据库中添加这个文件的信息
        const res = await KnowledgeBaseFile.create({
            knowledgeBaseId,
            filename: result[0].originalFilename,
            type,
            url: result[0].url,
            status: KnowledgeBaseFileStatus.WaitEmbedding,
            uploadTime: new Date(),
            metaData: {
                newFilename: result[0].newFilename,
            },
        })
        // 把文件向量化，保存到向量数据库中
        saveToVectorStore({
            knowledgeBaseId,
            url: result[0].url,
            knowledgeBaseFileId: res.id,
            collectionName,
            type,
        })

        ctx.body = { success: true, msg: '上传成功', data: res }
    } catch (error) {
        ctx.body = { success: false, msg: '发生错误' }
    }
}
